use std::fs;

use crate::datetime::DateTime;

// nerd font 
const ICON_PLG: &str = "";
const ICON_BA0: &str = " ";
const ICON_BA1: &str = " ";
const ICON_BA2: &str = " ";
const ICON_BA3: &str = " ";
const ICON_BA4: &str = " ";

// 更新频率: ms
const UPDATE_RATE: u64 = 60000;

// 电池信息相关文件路径
const BATTERY_STATUS_FILE: &str = "/sys/class/power_supply/BAT0/status";
const BATTERY_QUANTITY_FILE: &str = "/sys/class/power_supply/BAT0/capacity";

// 电池
pub struct Battery {
    // 电池图标
    icon: Vec<String>,
    // 电池电量等级
    level: usize,
    // 是否充电
    charge: bool,
    // 电池电量
    quantity: usize,
    // 更新时间
    timestamp: u64,
}

impl Battery {
    // 创建Battery
    pub fn new() -> Self {
        let battery = Battery {
            icon: vec![
                String::from(ICON_BA0),
                String::from(ICON_BA1),
                String::from(ICON_BA2),
                String::from(ICON_BA3),
                String::from(ICON_BA4),
                String::from(ICON_PLG),
            ],
            level: 0,
            charge: false,
            quantity: 0,
            timestamp: 0,
        };
        battery
    }

    // 获取展示字符串
    pub fn display(&mut self) -> String {
        self.update();
        if self.charge {
            format!(
                "{} {} {}%",
                self.icon[self.level], self.icon[5], self.quantity
            )
        } else {
            format!("{} {}%", self.icon[self.level], self.quantity)
        }
    }

    // 更新电池信息
    fn update(&mut self) {
        self.charge = Battery::battery_status();
        let current = DateTime::timestamp();
        if current - self.timestamp > UPDATE_RATE {
            self.quantity = Battery::battery_quantity();
            self.level = (self.quantity + 10) / 25;
            self.timestamp = current;
        }
    }

    // 获取电池状态
    fn battery_status() -> bool {
        if let Ok(content) = fs::read_to_string(BATTERY_STATUS_FILE) {
            content.contains("Charging")
        } else {
            eprintln!("get battery status failed!");
            true
        }
    }

    // 获取电池电量
    fn battery_quantity() -> usize {
        if let Ok(content) = fs::read_to_string(BATTERY_QUANTITY_FILE) {
            content.replace("\n", "").parse().unwrap()
        } else {
            eprintln!("get battery quantity failed!");
            100
        }
    }
}
